bitkeeper revision 1.289.2.3 (3f0aa9b8UnE6gBCHx3nuPzmgUovuqA)
authorsos22@labyrinth.cl.cam.ac.uk <sos22@labyrinth.cl.cam.ac.uk>
Tue, 8 Jul 2003 11:23:36 +0000 (11:23 +0000)
committersos22@labyrinth.cl.cam.ac.uk <sos22@labyrinth.cl.cam.ac.uk>
Tue, 8 Jul 2003 11:23:36 +0000 (11:23 +0000)
Split partition and device number parts of physdisk extent
id.

Also some minor sanity checking.

tools/internal/xi_phys_grant.c
tools/internal/xi_phys_probe.c
xen/drivers/block/xen_physdisk.c
xen/include/hypervisor-ifs/block.h
xenolinux-2.4.21-sparse/arch/xeno/drivers/block/xl_physdisk_proc.c
xenolinux-2.4.21-sparse/fs/partitions/xeno.c

index 92a4bf5014246371ff4839b9068575fa11abd200..58c00ed882200d759f2db9aa1dbdad95e4d9af52 100644 (file)
@@ -29,9 +29,10 @@ int main(int argc, char *argv[])
   else if (argv[1][1] == 'w')
     buf.mode |= 2;
   
-  buf.device = atol(argv[3]) + atol(argv[6]);
+  buf.device = atol(argv[3]);
   buf.start_sect = atol(argv[4]);
   buf.n_sectors = atol(argv[5]);
+  buf.partition = atol(argv[6]);
 
   asprintf(&strbuf, "/proc/xeno/dom%s/phd", argv[2]);
   fd = open(strbuf, O_WRONLY);
index 23c534c4d7bfdb83493119531dd455b17cbc869c..e38bb1634b8d08faaa5937de8cd443337546855c 100644 (file)
@@ -39,7 +39,8 @@ int main(int argc, char *argv[])
     for (x = 0; x < buf.n_aces; x++) {
       char read = ( buf.entries[x].mode & 1 ? 'r' : ' ' );
       char write = ( buf.entries[x].mode & 2 ? 'w' : ' ' );
-      printf("%x %lx %lx %c%c\n", buf.entries[x].device,
+      printf("%x %x %lx %lx %c%c\n", buf.entries[x].device,
+            buf.entries[x].partition,
             buf.entries[x].start_sect,
             buf.entries[x].n_sectors,
             read,
index c5d2deb82a491bce6a8b377f7b6b6bc95522dffd..2c7d7483b8246305a0e4014dbb92598a65fef785 100644 (file)
@@ -25,6 +25,7 @@ struct physdisk_ace {
   struct list_head list;
 
   unsigned short device;
+  unsigned short partition;
   unsigned long start_sect;
   unsigned long n_sectors;
   int mode;
@@ -40,8 +41,6 @@ static struct physdisk_ace *find_ace(const struct task_struct *p,
   struct list_head *cur_ace_head;
   struct physdisk_ace *cur_ace;
 
-  dev &= ~0x1f; /* ignore the partition part */
-
   list_for_each(cur_ace_head, &p->physdisk_aces) {
     cur_ace = list_entry(cur_ace_head, struct physdisk_ace,
                         list);
@@ -50,7 +49,7 @@ static struct physdisk_ace *find_ace(const struct task_struct *p,
            sect);
     if (sect >= cur_ace->start_sect &&
        sect < cur_ace->start_sect + cur_ace->n_sectors &&
-       dev == (cur_ace->device & ~0x1f) && /* ignore partition part */
+       dev == cur_ace->device &&
        ((operation == READ && (cur_ace->mode & PHYSDISK_MODE_R)) ||
         (operation == WRITE && (cur_ace->mode & PHYSDISK_MODE_W)))) {
       DPRINTK("Yes.\n");
@@ -85,7 +84,7 @@ static void xen_physdisk_revoke_access(unsigned short dev,
     ace_end = cur_ace->start_sect + cur_ace->n_sectors;
     if (cur_ace->start_sect >= kill_zone_end ||
        ace_end <= start_sect ||
-       (cur_ace->device & ~0x1f) != (dev & ~0x1f))
+       cur_ace->device != dev)
       continue;
     
     DPRINTK("Killing ace [%lx, %lx) against kill zone [%lx, %lx)\n",
@@ -111,7 +110,7 @@ static void xen_physdisk_revoke_access(unsigned short dev,
       /* Cut the current ace down to just the bit before the kzone,
         create a new ace for the bit just after it. */ 
       new_ace = kmalloc(sizeof(*cur_ace), GFP_KERNEL);
-      new_ace->device = dev & ~0x1f;
+      new_ace->device = dev;
       new_ace->start_sect = kill_zone_end;
       new_ace->n_sectors = ace_end - kill_zone_end;
       new_ace->mode = cur_ace->mode;
@@ -125,6 +124,7 @@ static void xen_physdisk_revoke_access(unsigned short dev,
 
 /* Hold the lock on entry, it remains held on exit. */
 static int xen_physdisk_grant_access(unsigned short dev,
+                                    unsigned short partition,
                                     unsigned long start_sect,
                                     unsigned long n_sectors,
                                     int mode,
@@ -143,6 +143,7 @@ static int xen_physdisk_grant_access(unsigned short dev,
     cur_ace->start_sect = start_sect;
     cur_ace->n_sectors = n_sectors;
     cur_ace->mode = mode;
+    cur_ace->partition = partition;
 
     list_add_tail(&cur_ace->list, &p->physdisk_aces);
   }
@@ -167,6 +168,7 @@ static void xen_physdisk_probe_access(physdisk_probebuf_t *buf,
       cur_ace = list_entry(cur_ace_head, struct physdisk_ace,
                           list);
       buf->entries[n_aces].device = cur_ace->device;
+      buf->entries[n_aces].partition = cur_ace->partition;
       buf->entries[n_aces].start_sect = cur_ace->start_sect;
       buf->entries[n_aces].n_sectors = cur_ace->n_sectors;
       buf->entries[n_aces].mode = cur_ace->mode;
@@ -196,6 +198,7 @@ int xen_physdisk_grant(xp_disk_t *xpd_in)
   }
   spin_lock(&p->physdev_lock);
   res = xen_physdisk_grant_access(xpd->device,
+                                 xpd->partition,
                                  xpd->start_sect,
                                  xpd->n_sectors,
                                  xpd->mode,
index 9f2b429adf1ed05bc77ec502ecbbc34c97d91afd..f5cf635afcad5b96030e8690be36ce3527471b2f 100644 (file)
@@ -149,18 +149,20 @@ typedef struct xp_disk
   int mode; /* 0 -> revoke existing access, otherwise bitmask of
               PHYSDISK_MODE_? constants */
   int domain;
-  unsigned short device;
+  unsigned short device; /* XENDEV_??? + idx */
+  unsigned short partition; /* partition number */
   unsigned long start_sect;
   unsigned long n_sectors;
 } xp_disk_t;
 
-#define PHYSDISK_MAX_ACES_PER_REQUEST 254
+#define PHYSDISK_MAX_ACES_PER_REQUEST 254 /* Make it fit in one page */
 typedef struct {
   int n_aces;
   int domain;
   int start_ind;
   struct {
-    unsigned short device;
+    unsigned short device; /* XENDEV_??? + idx */
+    unsigned short partition; /* partition number */
     unsigned long start_sect;
     unsigned long n_sectors;
     unsigned mode;
index d0a73cbeaddf856ab8a10b6de69d1f5b158859d3..1dd67653cbfecf21d9b8553b08aac3b02aa17915 100644 (file)
@@ -8,7 +8,35 @@
 #include <asm/uaccess.h>
 #include <linux/proc_fs.h>
 
+#include "xl_block.h"
+
 extern int xenolinux_control_msg(int operration, char *buffer, int size);
+extern unsigned short xldev_to_physdev(kdev_t xldev);
+
+static dev_t physdev_to_xldev(unsigned short physdev)
+{
+  switch (physdev & XENDEV_TYPE_MASK) {
+  case XENDEV_IDE:
+    switch (physdev & XENDEV_IDX_MASK) {
+    case 0 ... (XLIDE_DEVS_PER_MAJOR-1):
+      return MKDEV(XLIDE_MAJOR_0,
+                  (physdev & XENDEV_IDX_MASK) << XLIDE_PARTN_SHIFT);
+    case XLIDE_DEVS_PER_MAJOR ... (XLIDE_DEVS_PER_MAJOR * 2 - 1):
+      return MKDEV(XLIDE_MAJOR_1,
+                  (physdev & XENDEV_IDX_MASK) << XLIDE_PARTN_SHIFT);
+    }
+    break;
+  case XENDEV_SCSI:
+    return MKDEV(XLSCSI_MAJOR,
+                (physdev & XENDEV_IDX_MASK) << XLSCSI_PARTN_SHIFT);
+  case XENDEV_VIRTUAL:
+    return MKDEV(XLVIRT_MAJOR,
+                (physdev & XENDEV_IDX_MASK) << XLVIRT_PARTN_SHIFT);
+  }
+  printk(KERN_ALERT "Unrecognised xl device: %x\n", physdev);
+  BUG();
+  return -1;
+}
 
 static ssize_t proc_read_phd(struct file * file, char * buff, size_t size,
                             loff_t * off)
@@ -16,6 +44,7 @@ static ssize_t proc_read_phd(struct file * file, char * buff, size_t size,
   physdisk_probebuf_t *buf;
   int res;
   struct proc_dir_entry *pde;
+  int x;
 
   if (size != sizeof(physdisk_probebuf_t))
     return -EINVAL;
@@ -24,11 +53,6 @@ static ssize_t proc_read_phd(struct file * file, char * buff, size_t size,
   if (!buf)
     return -ENOMEM;
 
-  if (copy_from_user(buf, buff, size)) {
-    kfree(buf);
-    return -EFAULT;
-  }
-
   pde = file->f_dentry->d_inode->u.generic_ip;
   buf->domain = (int)pde->data;
 
@@ -43,6 +67,8 @@ static ssize_t proc_read_phd(struct file * file, char * buff, size_t size,
   if (res)
     res = -EINVAL;
   else {
+    for (x = 0; x < buf->n_aces; x++)
+      buf->entries[x].device = physdev_to_xldev(buf->entries[x].device);
     res = sizeof(physdisk_probebuf_t);
     if (copy_to_user(buff, buf, sizeof(physdisk_probebuf_t))) {
       res = -EFAULT;
@@ -75,6 +101,7 @@ static int proc_write_phd(struct file *file, const char *buffer,
 
   pde = file->f_dentry->d_inode->u.generic_ip;
   xpd->domain = (int)pde->data;
+  xpd->device = xldev_to_physdev(xpd->device);
 
   res = xenolinux_control_msg(XEN_BLOCK_PHYSDEV_GRANT, local, count);
   if (res == 0)
index 2ddc71b4d1a42ee0adf76b27b7dca11ece3e237e..b1e4d068f173417a8dc0f2bb546ff8de601fb787 100644 (file)
@@ -43,18 +43,18 @@ int xeno_partition(struct gendisk *hd,
   count = 0;
 
   for (i = 0; i < buf->n_aces; i++) {
-    if ((buf->entries[i].device & 0x1f) == 0)
+    if (buf->entries[i].partition == 0)
       continue;
     /* Make sure the partition is actually supposed to be on this
        disk.  This assumes that Xen and XenoLinux block device
        numbers match up. */
-    if ((buf->entries[i].device & ~0x1f) != bdev->bd_dev)
+    if (buf->entries[i].device != bdev->bd_dev)
       continue;
     /* This is a bit of a hack - the partition numbers are specified
        by the hypervisor, and if we want them to match up, this is
        what we need to do. */
     count ++;
-    minor = (buf->entries[i].device & 0x1f) + first_part_minor - 1;
+    minor = buf->entries[i].partition + first_part_minor - 1;
     add_gd_partition(hd,
                     minor,
                     buf->entries[i].start_sect,